﻿using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Windows;
using System.Xml.Serialization;
using TciNewsReader_2014_04.Interfaces;
namespace TciNewsReader_2014_04.Infrastructure
{
    public class PersistenceManager : IPersistenceManager
    {
        private const string MyName = "Persistence manager";
        private static readonly XmlSerializer Serializer;
        private readonly IExceptionHandler _exceptionHandler;
        static PersistenceManager()
        {
            Serializer = new XmlSerializer(typeof (List<string>));
        }
        public PersistenceManager(IExceptionHandler exceptionHandler)
        {
            _exceptionHandler = exceptionHandler;
        }
        public bool FileExists()
        {
            return File.Exists(Constants.UrlFileLocation);
        }
        public void SaveUrlList(List<string> urls)
        {
            try
            {
                using (var sw = new StreamWriter(Constants.UrlFileLocation))
                {
                    Serializer.Serialize(sw, urls);
                }
            }
            catch (Exception exception)
            {
                _exceptionHandler.HandleException(exception, MyName);
            }
        }
        public List<string> DefaultList()
        {
            var result = new List<string> {Constants.FallbackFeedPublisher};
            return result;
        }
        public void GetUrlList(Action<List<string>> onComplete)
        {
            bool useDefaultList = false;
            List<string> result = DefaultList();
            if (File.Exists(Constants.UrlFileLocation))
            {
                try
                {
                    using (var sr = new StreamReader(Constants.UrlFileLocation))
                    {
                        result = Serializer.Deserialize(sr) as List<string>;
                        if (result == null)
                        {
                            useDefaultList = true;
                        }
                        else
                        {
                            result = result.OrderBy(q => q).ToList();
                        }
                    }
                }
                catch (Exception ex)
                {
                    _exceptionHandler.HandleException(ex, MyName);
                    useDefaultList = true;
                }
            }
            else 
            { 
                _exceptionHandler.HandleException(new Exception("Cannot locate initialisation file " + Constants.UrlFileLocation + ". Using fallback"), MyName );
                useDefaultList = true;
            }
            if (useDefaultList)
            {
                result = DefaultList();
            }
            if (onComplete != null)
            {
                onComplete(result);
            }
        }
    }
    public class WindowPositionSaver
    {
        private const string MyName = "Window position saver";
        private static readonly XmlSerializer Serializer = new XmlSerializer(typeof(WindowInfo));
        private readonly IExceptionHandler _exceptionHandler;
        public WindowPositionSaver(IExceptionHandler exceptionHandler)
        {
            _exceptionHandler = exceptionHandler;
        }
        public void RestoreWindowPosition(Window w)
        {
            try
            {
                if (File.Exists(Constants.WindowInfoLocation))
                {
                    using (StreamReader sr = new StreamReader(Constants.WindowInfoLocation))
                    {
                        WindowInfo wi = Serializer.Deserialize(sr) as WindowInfo;
                        if (wi != null)
                        {
                            wi.Coerce();
                            w.SetValue(Window.LeftProperty, wi.Left);
                            w.SetValue(Window.TopProperty, wi.Top);
                            w.SetValue(Window.HeightProperty, wi.Height);
                            w.SetValue(Window.WidthProperty, wi.Width);
                        }
                    }
                }
            }
            catch (Exception ex)
            {
                _exceptionHandler.HandleException(ex, MyName);
            }
        }
        public void SavedWindowPosition(Window w)
        {
            try
            {
                WindowInfo wi = new WindowInfo();
                wi.Left = (double)w.GetValue(Window.LeftProperty);
                wi.Top = (double)w.GetValue(Window.TopProperty);
                wi.Height = (double)w.GetValue(Window.HeightProperty);
                wi.Width = (double)w.GetValue(Window.WidthProperty);
                wi.Coerce();
                using (StreamWriter sw = new StreamWriter(Constants.WindowInfoLocation))
                {
                    Serializer.Serialize(sw, wi);
                }
            }
            catch (Exception ex)
            {
                _exceptionHandler.HandleException(ex, MyName);
            }
        }
        public class WindowInfo
        {
            public WindowInfo()
            {
                Left = Top = 0;
                Width = 1000;
                Height = 600;
            }
            public double Left { get; set; }
            public double Top { get; set; }
            public double Width { get; set; }
            public double Height { get; set; }
            public void Coerce()
            {
                Left = Math.Max(0, Math.Min(1000, Left));
                Top = Math.Max(0, Math.Min(1000, Top));
                Width = Math.Max(0, Math.Min(1200, Width));
                Height = Math.Max(0, Math.Min(1000, Height));
            }
        }
    }
}
